# Regression Template

# Multiple Linear Regression
from pandas import DataFrame as df
import numpy as np
import matplotlib.pyplot as plt
import pandas as pd
import datetime
from sklearn.metrics import mean_squared_error
from matplotlib.pylab import rcParams
from sklearn.svm import SVR
rcParams['figure.figsize'] = 11, 4
# Importing the datasets
# #定义一个将时间转为数字的函数,s为字符串
#用pandas将时间转为标准格式
def datestr2num(s):
 #toordinal()将时间格式字符串转为数字
    return datetime.datetime.strptime(s,'%Y-%m').toordinal()

dateparse = lambda dates: pd.datetime.strptime(dates,'%Y-%m-%d')


   
writer = df(columns = ["FORECAST1", "FORECAST2", "FORECAST3" , "FORECAST4" , "FORECAST5" , "FORECAST6" , "RMSE" ])
writer.index.name = "Window"

#读取原数据
org_f = open('Corn.csv')
org_datasets = pd.read_csv(org_f,date_parser=dateparse)

X = []
org_Y = []
#new_date = []

for i in range(org_datasets.shape[0]):
    X_convert = int(datestr2num(str(org_datasets.iloc[i,0])))
    #new_date.append(X_convert)
    X.append(X_convert)
    org_Y.append(org_datasets.iloc[i,1].astype(np.float32))
org_Y = np.array(org_Y).astype(np.float32)
X = np.array(X).astype(np.float32)
org_Y = org_Y.reshape(-1,1)
X = X.reshape(-1,1)

#preprocessing.scale()作用：
#scale()是用来对原始样本进行缩放的，范围可以自己定，一般是[0,1]或[-1,1]。
#缩放的目的主要是
#1）防止某个特征过大或过小，从而在训练中起的作用不平衡；
#2）为了计算速度。因为在核计算中，会用到内积运算或exp运算，不平衡的数据可能造成计算困难。
from sklearn.preprocessing import StandardScaler
sc_X = StandardScaler()#去均值和方差归一化。且是针对每一个特征维度来做的，而不是针对样本。
#sc_Y = StandardScaler()
X = sc_X.fit_transform(X)#可以保存训练集中的参数（均值、方差）直接使用其对象转换测试集数据。
#Y = sc_Y.fit_transform(Y)

steps = 6   # steps = 预测步数
data_index = 0  # data_index = 数据个数    

#重构数据预测集

window = 36

filepath = "Corn"+str(window)+".csv"
f = open(filepath)
datasets = pd.read_csv(f,date_parser=dateparse)
  
Y = []
   
    
data_index = datasets.shape[0]


#从重构数据读取重构价格
for i in range(datasets.shape[0]):
    Y_convert = datasets.iloc[i,1].astype(np.float32)
    Y.append(Y_convert)


Y = np.array(Y).astype(np.float32)
    

"""# Splitting the dataset into the Training set and Test set

from sklearn.model_selection import train_test_split
X_Train, X_Test, Y_Train, Y_Test = train_test_split(X, Y, test_size = 0.2, random_state = 0)
"""
#给予数组一个新的形状,而不修改它的数据
Y = Y.reshape(-1,1)

# Fitting the SVR model to the dataset


#C表征你有多么重视离群点，C越大越重视，越不想丢掉它们
#gamma:是’rbf’，’poly’和’sigmoid’的核系数且gamma的值必须大于0。随着gamma的增大，
#存在对于测试集分类效果差而对训练分类效果好的情况，并且容易泛化误差出现过拟合。如图发现gamma=0.01时准确度最高。
    
regressor =  SVR(kernel="rbf",gamma=0.5041127244117016,C=87.58580701028254)


# fit(x,y)传两个参数的是有监督学习的算法，fit(x)传一个参数的是无监督学习的算法，比如降维、特征提取、标准化
#用重构数据进行训练
regressor.fit(X[:data_index],Y[:data_index])

#如果y值有规范化，需要反转
#preY=sc_Y.inverse_transform(regressor.predict(X))
#Y=sc_Y.inverse_transform(Y)
# Predicting a new result with the Polynomial Regression 
#Y_Pred = sc_Y.inverse_transform(regressor.predict(sc_X.transform(np.array([6.5]).reshape(-1,1))))

# Visualising the Regression results

X_plot = np.linspace(0, data_index + steps, data_index + steps)[:, None]
   
#预测
predict = regressor.predict(X[data_index:data_index + steps])
#误差分析
MSE= mean_squared_error(predict, org_Y[data_index:data_index + steps])
#MSE= mean_squared_error(regressor.predict(X)[data_index:data_index + steps], org_Y[data_index:data_index + steps])
RMSE = MSE**0.5
print("重构数据与原数据的  RMSE " + str(RMSE))

#for temp in range(steps):
#    col = "FORECAST" + str(temp+1)
#    writer.loc[window,col] =  predict[temp]
#writer.loc[window,"RMSE"] =  RMSE

#plt.figure(figsize=(11,4))
#plt.plot(X_plot[:data_index+ steps],org_Y[:data_index+ steps], color = 'red') #输出原价格曲线


#plt.plot(X_plot[data_index:data_index + steps], predict, color = 'blue') #输出预测区间 
#plt.title('Reconstrutc   MSE: %.4f'% MSE + '   RMSE: %.4f'% RMSE)
#plt.xlabel('Month')
#plt.ylabel('Price')
#plt.show()
#plt.savefig("G:/大创/运行图/SVR/price2.jpg")
    


fit_data = regressor.predict(X[:data_index + steps])

ts = pd.read_csv('Corn.csv', parse_dates=True, index_col='Month')
new_index = pd.date_range(start=ts.index.min(),periods=fit_data.shape[0], freq="MS")
forecast_df = pd.DataFrame(fit_data, columns=['svr'], index=new_index)
forecast_df.to_csv("svr_integration"+".csv")

